home *** CD-ROM | disk | FTP | other *** search
Text File | 1990-06-24 | 46.0 KB | 2,158 lines | [TEXT/MPS ] |
- *******************************************************************************
- *
- * fakeModalDialog and other supporting access routines and such.
- * Version 3.0
- *
- * Copyright (c)
- * Apple Computer, Inc. 1989-1990
- * All Rights Reserved.
- *
- * Written by Eric Soldan.
- *
- * Developer Technical Support Apple II Sample Code
- *
- * The purpose of this code is to handle dialogs in a variety of ways
- * that are more robust than what the toolbox offers. It also supports
- * the new movable/modeless dialog types described in the latest human
- * interface guidelines.
- *
- *******************************************************************************
- *
- * Here is some C sample code that uses fakeModalDialog. This code is
- * for an about box. What is different about this about box is that
- * you can use menus while the about box is on the screen. This means
- * that you can use desk accessories while the about box is active.
- * It also means that you can quit the application at this time.
- * You can also close the about box with the close menu option.
- *
- * This sample uses the modal mode with menus for the about box. Since
- * menus are available, there is more support (code) necessary from the
- * application. The application has to detect that the user chose
- * close from the menu and take appropriate action, for example.
- *
- * First, a little about fakeModalDialog:
- *
- * fakeModalDialog returns a long as a result.
- * If the result is NULL:
- * Nothing happened. Unlike ModalDialog, control is returned to
- * the application during null events. This is so the application
- * can do stuff like switch cursors, or other idle tasks.
- * If bit 31 of the result is true:
- * The user chose a menu item. Bits 0-15 are the menu item ID.
- * Bits 16-30 are the menu ID.
- * If bit 31 of the result is false:
- * The user clicked on a control. Bits 0-30 are the control ID.
-
- * Now, the sample code fragment:
-
- * #define aboutBoxID 0x1001L
- *
- * void doAboutBox()
- * {
- * WindowPtr wptr, keepPort;
- * unsigned long id;
- * unsigned int item;
- * keepPort = GetPort(); /* Preserve the current port. */
- *
- * wptr = NewWindow2(NULL, NULL, NULL, NULL, 2, aboutBoxID, rWindParam1);
- * /* Open the about box from a resource. */
- *
- * if (!_toolErr) { /* If the window opened successfully... */
- * aboutWindow = wptr; /* Set the aboutWindow global variable. */
- * /* This tells other routines what state */
- * /* we are in. */
- *
- * for (;;) { /* Loop, due to NULL events being returned. */
- *
- * id = fakeModalDialog(
- * &event, /* Pointer to extended event record. */
- * NULL, /* Use default update procedure. */
- * NULL, /* There will be no event mods. */
- * NULL, /* Do standard beep. */
- * fmdMenuSelect+ /* Allow pullDowns. */
- * fmdMenuKey+ /* Allow menu keys. */
- * fmdDeskAcc+ /* Allow desk accessories. */
- * fmdUpdateAll /* Update all windows, not just about. */
- * );
- *
- * item = id; /* Get lo-word from result. */
- *
- * if (id & 0x80000000L) { /* If menu command... */
- * if (item == 255) { /* If close command then */
- * HiliteMenu(0, FileMenuID); /* turn menu inv. off. */
- * break; /* Go close about box. */
- * }
- * doMenuCommand(id); /* Do other menus (like quit). */
- * if (quitFlag) break; /* User did do a quit from menu. */
- * }
- * else { /* ...else handle controls. */
- * if (item == 1) break; /* User clicked OK button. */
- * }
- * }
- *
- * SetPort(keepPort); /* Put port back before closing about. */
- * CloseWindow(wptr); /* Close aboutBox. */
- * aboutWindow = NULL; /* Let others know it is closed. */
- * appSetMenus(); /* Update the menus to reflect a new. */
- * } /* top window. */
- * }
-
- * An interesting point here is the call to appSetMenus. This is a routine
- * in the application that is responsible for putting the menus in the
- * correct state. fakeModalDialog automatically calls this routine (if told
- * to) whenever an activate event occurs that it gets a chance to see.
- * fakeModalDialog may not see the activate event only if a desk accessory
- * is open, just behind the about box. When the about box is closed, the
- * desk accessory gets the activate event. fakeModalDialog never got an
- * activate event, so it didn't know to call the menu update routine. This
- * situation can only occur when a desk accessory is just behind the window
- * to be closed. As a safe rule, whenever a window is closed, the menu
- * update routine should be called by the application. (Something like this
- * should be done anyway.)
-
- * To tell fakeModalDialog to automatically call a menu update routine when
- * it gets an activate event, make a call to fmdSetMenuProc. For an application
- * menu update routine called appSetMenus, you would tell fakeModalDialog
- * about it by the following:
- * fmdSetMenuProc(appSetMenus);
- * To turn off menu updating again, do this:
- * fmdSetMenuProc(NULL);
-
- * fmdEditMenu figures the state of cut, copy, paste, and clear in
- * the edit menu based on the state of controls in the window.
- * It looks up the target control (either lineEdit or textEdit) and
- * then sets the states appropriately. For lineEdit, if anything
- * is selected, then cut, copy and clear are available. If there is
- * anything in the scrap, then paste is also available. TextEdit
- * works the same way, unless the textEdit control is a read-only
- * control. In that case, cut, paste, and clear are not available.
- * If there is no lineEdit or textEdit control, then the state of
- * these menu items is left alone. The application needs to take care
- * of them in that case. (It is possible that there are custom
- * controls for the application that can use these menu items, and
- * there is no way for fakeModalDialog to know about them. Therefore
- * the correct thing to do is to do nothing.)
-
- * fmdFindCursorCtl is used to find which control is at a certain point.
- * The toolbox call FindControl can't be used for this because textEdit
- * controls become active when called with a point in them. That is not
- * the desired effect of fmdFindCursorCtl. If you just want to know what
- * control you are over and have nothing affected, then use this entry
- * point. It is used by fakeModalDialog to determine whether or not to
- * display an i-beam cursor. If the i-beam bit is set and the user moves
- * the mouse over a lineEdit or textEdit control, then the cursor changes
- * to an i-beam. Note that the scrollbars for a textEdit control are
- * considered a separate control. This is so that the cursor stays
- * an arrow when over the scrollbars.
-
- * Back to fakeModalDialog:
-
- * Some sample calls (in C) would look like:
- * ctlID = fakeModalDialog(&event, NULL, NULL, NULL, 0);
- * ctlID = fakeModalDialog(&event, updateProc, NULL, -1L, 0);
- * ctlID = fakeModalDialog(&event, updateProc, eventHook, beepProc, flags);
- *
- * The parameters are:
- *
- * event: A pointer to an extended (for 5.0) event record.
- * updateProc: Pointer to function to update the window. Pass a NULL for
- * default. (The default entry point is called fmdStdDrawProc.)
- * eventHook: Pointer to function that is called after the GetNextEvent
- * call and before any processing occurs on that event. This
- * is more useful than a filter. You can simply change the
- * event by changing the event record. For example: Let's say
- * that you want to be able to cancel a modal dialog by pressing
- * either openApple-period or ESC. The problem is that,
- * although you can have two key equivalents for a
- * super-control, theway that modifiers are determined is the
- * same for both keys. This means that you can't have
- * openApple-period and ESC asyour two key equivalents. With
- * this event hook, you can lookat the event, and if it is the
- * openApple-period, you can simply change the event record so
- * that it is an ESC with no openApple modifier. Then when you
- * return to fakeModalDialog, it will handle the event as if the
- * user simply typed an ESC. By using this technique, you can
- * have as many modifiers as you want. If you wish to filter
- * out an event, you would simply changethe event type to a
- * NULL event.
- * beepProc: Pointer to custom beep function. fakeModalDialog calls this
- * if there is any mouseDown outside the window, just like
- * ModalDialog.If you wish it to beep like ModalDialog, pass a
- * NULL. If you wish it to do nothing, pass a -1.
- * If you wish a custom beep function, pass it a pointer to
- * that function.
- * flags, bit 0: Cut/Copy/Paste for lineEdit items would normally involve
- * the scrap. When this bit is true, the scrap is not involved
- * when using lineEdit items. This may be useful to protect a
- * large scrap for an application from being hit with something
- * trivial.
- * bit 1: If true, allow menu pullDowns for movable/modal dialogs.
- * If they are allowed, then the return value is the menu
- * item ID (low-word) and the menu ID (hi-word). To
- * distinguish from ctlID's, thehi-bit (bit 31) is set. This
- * means that if you are allowing menu selections, you can't have
- * any menu ID's with a hi-bit-on ID. It also means that you
- * can't have controls with bit 31 on either.
- * bit 2: If true, allow menu keys. Return values work the same as for
- * pullDowns.
- * bit 3: If true, use i-beam cursor for lineEdit & textEdit ctls.
- * Otherwise, use an arrow cursor everywhere.
- * bit 4: If true, automatically handle desk accessories. This means
- * that bit 1 must be true to have fakeModalDialog open the DA.
- * If the DA is already open, the user can click on it, and it
- * will become active, even if bit 1 is false.
- * bit 14: If true, update all windows. The toolbox call ModalDialog
- * does not update other windows. This takes away a lot of the
- * point of movable/modal dialogs. The whole point is so that
- * you can see what is behind it. When you move the dialog, if
- * the windows in back didn't update, then there would be no
- * point in moving the window. If you want, you can set this
- * bit false, and it will update only the front-most
- * application window.
- * bit 15: This is the bit that determines whether or not a dialog is
- * movable. If it is true, then the dialog is movable. To be
- * moved, however, it has to have a title bar (the drag region)
- * and it has to have the fMove bit set. Without these also,
- * the window still won't be able to be moved.
- *
- * ctlID: Control that was hit, or menu that was chosen.
- * bit 31 off, it is a control ID.
- * bit 31 on, it is a menu ID (hi-word), menu item ID (lo-word).
- *
- * There is one more thing to worry about, and that is the border of the window.
- * The window manager doesn't allow you have an alert frame and a title at the
- * same time. If you set both of these bits in the wFrameBits field, then the
- * alert border is drawn wrong. It would be ideal for fakeModalDialog if this
- * restriction didn't exist. Then the window attributes all could be chosen via
- * the window frame bits in a resource. Unfortunately, this isn't the case. To
- * manage this restriction, the default update procedure, under certain
- * conditions, draws the alert frame itself. If fAlert is set, then the alert
- * border isn't drawn by the default update procedure. The update procedure
- * doesn't have to draw it, since it is automatically drawn by the window
- * manager. If fAlert is set, then the dialog doesn't have a title bar, due to
- * the window manager restriction. If fAlert isn't set, then the default update
- * procedure draws the alert border. The alert border is drawn as part of the
- * content of the window. Due to this, the coordinates you use for the content
- * of the window have to be a little different, to make space for the border.
- * The upper-left-hand corner of the window is really 10,4, (4,4 for 320 mode)
- * instead of 0,0. So far, we have discussed how the alert border gets drawn,
- * either by the window manager, or by the default update procedure for
- * fakeModalDialog. It is possible that you don't want an alert border at all.
- * If you don't, then fAlert should be off, and you should turn on fFlex. fFlex
- * was used because it should be able to be set from a resource, and all other
- * bits would have an adverse effect. Dialogs don't have grow boxes and zoom
- * boxes, so fFlex is meaningless for dialogs (until now).
-
- ***********************************************************************
-
- case on
-
- INCLUDE 'm16.util2'
- INCLUDE 'e16.types'
-
- INCLUDE 'e16.control'
- INCLUDE 'm16.control'
- INCLUDE 'm16.desk'
- INCLUDE 'e16.event'
- INCLUDE 'm16.event'
- INCLUDE 'e16.lineedit'
- INCLUDE 'm16.lineedit'
- INCLUDE 'm16.memory'
- INCLUDE 'm16.menu'
- INCLUDE 'm16.misctool'
- INCLUDE 'm16.quickdraw'
- INCLUDE 'm16.scrap'
- INCLUDE 'm16.textedit'
- INCLUDE 'e16.window'
- INCLUDE 'm16.window'
-
- longi on
- longa on
-
- ***********************************************************************
-
- fmdNoScrapForLE equ $0001
- fmdMenuSelect equ $0002
- fmdMenuKey equ $0004
- fmdIBeam equ $0008
- fmdDeskAcc equ $0010
- fmdUpdateAll equ $4000
- fmdMovable equ $8000
-
- export fakeModalDialog
- fakeModalDialog PROC
- export FAKEMODALDIALOG
- export fmdGetCtlPart, FMDGETCTLPART
- import fmdEditMenu, fmdFindCursorCtl
- import fmdStdDrawProc, fmdGetMenuProc
- import fmdIBeamCursor, fmdGetIBeamAdr
- import _fmdNoError
-
- DefineStack
-
- dlgwptr long ;Must be at 1,s
- keepPort long ;Must be at 5,s
- ctlHndl long
- ctlPtr long
- theHndl long
- thePtr long
- whichWindow long
- tempwptr long
- code word
- editTask word
- yloc word
- xloc word
- wkind word
- menunum word
- zero word
-
- sizeLocals EndLocals
-
- saveDPage word
- returnAddr block 3
-
- BegParms
- flags word ;bit 0 = 0, involve scrap for
- ; lineEdit items.
- ;bit 0 = 1, don't involve scrap for
- ; lineEdit items.
- ;bit 1 = 0, don't do _MenuSelect for
- ; movable/modal dialogs.
- ;bit 1 = 1, do _MenuSelect for
- ; movable/modal dialogs.
- ;bit 2 = 0, don't do _MenuKey for
- ; movable/modal dialogs.
- ;bit 2 = 1, do _MenuKey for
- ; movable/modal dialogs.
- ;bit 3 = 0, use arrow cursor
- ; everywhere.
- ;bit 3 = 1, use i-beam cursor for
- ; lineEdit & textEdit ctls.
- ;bit 4 = 0, let app handle desk
- ; accessories.
- ;bit 4 = 1, automatically handle desk
- ; accessories.
- ;bit 14 = 0, Don't update other
- ; application windows.
- ;bit 14 = 1, Update all windows.
- ;bit 15 = 0, Modal window.
- ;bit 15 = 1, movable/modal window.
- beepProc long ;Null, SysBeep. Negative, do nothing.
- eventHook long ;Optional -- pass a NULL for none.
- updateProc long ;Optional -- pass a NULL for default.
- event long ;Must be extended 5.0 event rec ptr.
- sizeParms EndParms
-
- retval long ;Control ID hit. NULL if none.
- ;If bit 31 is on, then retval
- ;is a menu ID.
- ***
-
- FAKEMODALDIALOG phd ;Save directPage register.
- tsc ;Make space for locals.
- sec
- sbc #sizeLocals
- tcs
- tcd ;Set directPage register.
-
- pla
- pla
- _GetPort ;Result space already there (keepPort).
-
- pha
- pha
- _FrontWindow ;Result space already there (dlgwptr).
-
- pha ;Find out if it is a DA window.
- pei dlgwptr+2
- pei dlgwptr
- _GetWKind
- pla
- sta wkind
- bpl @gotit
-
- @get1stRegWnd pha ;Result space for _GetWFrame.
-
- pha ;Result space for _GetNextWindow.
- pha
-
- pei dlgwptr+2
- pei dlgwptr
- _GetNextWindow
-
- lda 1,s ;Param for _GetWFrame.
- sta dlgwptr
- lda 3,s
- sta dlgwptr+2
-
- _GetWFrame
- pla
-
- and #fVis
- beq @get1stRegWnd ;Window is invisible, so skip it.
-
- pha
- pei dlgwptr+2
- pei dlgwptr
- _GetWKind
- pla
- bmi @get1stRegWnd ;Window is system window, so skip it.
-
- @gotit stz retval ;Assume nothing interesting is
- stz retval+2 ;going to happen.
- stz code
- stz editTask ;For cut/copy/paste/clear signal.
- stz zero ;For optimization purposes.
-
- lda updateProc+1 ;Set up the update procedure for all
- bne @a ;cases. This also sets it up so that
- ;TaskMaster can handle this window
- ;from other parts of the application.
-
- lda #fmdStdDrawProc>>16
- sta updateProc+2
- lda #fmdStdDrawProc
- sta updateProc ;Use the default update procedure.
- @a pei updateProc+2
- pei updateProc
- pei dlgwptr+2
- pei dlgwptr
- _SetContentDraw ;Let the window and TaskMaster know.
-
- @aa pha ;Make sure that top window is
- pha ;the active window.
- _GetPort
- pla
- sta keepPort
- pla
- sta keepPort+2
- pei dlgwptr+2
- pei dlgwptr
- _SetPort
-
- lda flags
- and #fmdIBeam
- beq @b ;No cursor changes.
-
- lda wkind
- bmi @b
-
- pha ;Result space for control part.
-
- ldy #0 ;Point to where to put the handle.
- phy
- tdc
- clc
- adc #ctlHndl
- pha ;Pointer to ctlHndl now on stack.
-
- phy
- adc #yloc-ctlHndl
- pha ;Pointer to yloc now on stack.
- _GetMouse
-
- pei xloc ;Now that they are right, pass 'em on.
- pei yloc
- pei dlgwptr+2
- pei dlgwptr
- jsl fmdFindCursorCtl ;Find which control cursor is over.
- pla ;The part code, which we don't care
- ;about here.
-
- beq @arrowCursor ;Not over any control -- use arrow.
-
- jsr getCtlProc ;Find out what kind of control it is.
- cmp #editTextControl>>16
- beq @ibeamCursor ;It is a TextEdit ctl, kind of
- ;See fmdFindCursorCtl for more info.
- cmp #editLineControl>>16
- beq @ibeamCursor ;It is a LineEdit tool.
-
- @arrowCursor jsr ibeamTest
- bcc @b
- _InitCursor
- bra @b ;We have an arrow cursor.
-
- @ibeamCursor jsr ibeamTest
- bcs @b ;We have an ibeam cursor.
- jsl fmdIBeamCursor
-
- @b _SystemTask
-
- lda flags ;See if cut/copy/paste is tied to menu.
- and #fmdMenuSelect+fmdMenuKey
- beq @c ;Isn't keyDownEvt or mouseDownEvt.
- jsl fmdEditMenu ;Update the edit menu.
-
- @c pha ;Get the event.
- pea $FFFF
- pei event+2
- pei event
- _GetNextEvent
- pla
- beq @exit ;Event shouldn't be handled by app.
-
- ldy #owhat
- lda [event],y
- sta code
- bne @gotEvent
-
- @exit lda code ;See if code is 0. If it is, force a
- bne @exit0 ;NULL event, so the cursor will flash
- ldy #owhat ;for lineedit items, etc.
- sta [event],y
- pha
- pea 1
- pha
- pha
- pei event+2
- pei event
- _SendEventToCtl
- pla
-
- @exit0 pei keepPort+2
- pei keepPort
- _SetPort
- tsc ;Get rid of local variables.
- clc
- adc #sizeLocals
- tcs
- pld ;Restore directPage register.
- lda 1,s ;Move return address.
- sta 1+sizeParms,s
- lda 2,s
- sta 2+sizeParms,s
- tsc ;Get rid of passed parameters.
- adc #sizeParms
- tcs
- jml _fmdNoError
-
- @gotEvent lda eventHook+1
- beq @noEventHook ;Zero, no event massaging.
-
- pei event+2 ;Give the event hook something
- pei event ;to play with.
- phk ;Push where we want to return to.
- pea @noEventHook-1
-
- pha ;Push the eventHook address and return
- phb ;to it.
- pla
- lda eventHook
- dec a
- pha
- rtl
-
- @noEventHook ldy #owhat
- lda [event],y
- sta code
-
- jsr doMouseDown
- bcc @exit
-
- jsr doMenuKey
- bcc @exit ;The key was a menu key.
-
- jsr doCutCopyPaste
- bcc @exit ;We did a cut, copy, or paste.
-
- jsr doActivate
- bcc @exit ;We did an activate.
-
- jsr doUpdate
- bcc @exit ;We did an update.
-
- pha
- lda #0
- pha
- pha
- pha
- pei event+2
- pei event
- _SendEventToCtl
- pla
- beq @exit0
-
- ldy #owmTaskData2 ;Get the ctl hndl of affected ctl.
- lda [event],y
- sta ctlHndl ;Save this in ctlHndl.
- iny
- iny
- lda [event],y
- sta ctlHndl+2
- jsr setValues
- brl @exit
-
- ***
-
- doCutCopyPaste lda editTask ;We already have a task,
- bne @atask ;so don't check keypress.
-
- lda code
- cmp #keyDownEvt
- beq @akey
- cmp #autoKeyEvt
- beq @akey
-
- @secexit sec
- rts
-
- @akey lda flags
- and #fmdMenuKey
- bne @secexit
- ldy #omodifiers ;See if it is a cut/copy/paste command.
- lda [event],y
- and #controlKey+optionKey+appleKey
- cmp #appleKey
- bne @secexit ;Wrong modifiers -- no go.
-
- ldy #omessage
- lda [event],y
- ora #$20 ;Lower-case it.
-
- ldx #251
- cmp #'x'
- beq @yes
- inx
- cmp #'c'
- beq @yes
- inx
- cmp #'v'
- sec
- bne @secexit
- @yes stx editTask ;We have a valid task now.
-
- @atask pha ;Find out what control we are talking
- pha ;about.
- _FindTargetCtl
- ply
- sty ctlHndl
- ply
- sty ctlHndl+2
- bcs @secexit
-
- lda editTask ;251 thru 254 (cut/copy/paste/clear)
- stz editTask ;This is also a flag, so we need to set
- sec ;it back.
- sbc #251-4
- asl a ;Assume TextEdit.
- tax
- stz theHndl
- stz theHndl+2
-
- jsr getCtlProc ;Find out what tool it is.
- cmp #editTextControl>>16
- beq @b ;It is TextEdit, and the xreg is set up
- ;for TextEdit.
-
- cmp #editLineControl>>16
- bne @secexit ;Not a LineEdit tool, so there can be
- ;no cut/copy/paste.
-
- ldy #octlData ;It is LineEdit.
- lda [ctlPtr],y
- sta theHndl
- iny
- iny
- lda [ctlPtr],y
- sta theHndl+2
- txa
- and #7
- tax ;LineEdit tool.
-
- @b pei theHndl+2 ;All the below routines will use this
- pei theHndl ;parameter eventually.
- jmp (@theTask,x)
-
- @theTask dc.w @leCut, @leCopy, @lePaste, @leClear
- dc.w @teCut, @teCopy, @tePaste, @teClear
-
- @leCut _LECut ;Do the cut.
- @leCut0 lda flags
- lsr a
- bcs @clcexit
- _ZeroScrap ;Then conditionally do the LEToScrap.
- pha ;Conditionally, because of the bug for
- _LEGetScrapLen ;zero-length scrap.
- pla
- beq @clcexit
- _LEToScrap
- @clcexit clc
- rts
- @clcexitz pla
- pla
- clc
- rts
-
- @leCopy _LECopy ;Do the copy.
- bra @leCut0
-
- @lePaste lda flags
- lsr a
- bcs @c
-
- pha ;Boy, are we good citizens, or what?
- pha
- pei zero
- _GetScrapSize
- plx
- ply
- bcs @clcexitz ;Give up and do nothing.
- tya
- bne @clcexitz ;Way too big, so give up.
- txa
- beq @clcexitz ;Too small, so give up.
- _LEFromScrap
- bcs @clcexitz ;Somebody wasn't pleased, so give up.
- @c _LEPaste
- clc
- rts
-
- @leClear _LEDelete ;Do the clear.
- clc
- rts
-
- @teCut ldy #$28+2 ;Find out if we are read-only.
- lda [ctlPtr],y
- and #$0400 ;Bit 26, please.
- beq @teCut0 ;Not read-only, so it is okay.
- pla
- pla
- bra @teCut1
- @teCut0 _TECut ;Do the cut.
- @teCut1 clc
- rts
-
- @teCopy _TECopy ;Do the copy.
- clc
- rts
-
- @tePaste _TEPaste ;Do the paste.
- clc
- rts
-
- @teClear _TEClear ;Do the clear.
- clc
- rts
-
- getCtlProc ldy #2 ;Find out what tool it is.
- lda [ctlHndl],y
- sta ctlPtr+2
- lda [ctlHndl]
- sta ctlPtr ;Handle now dereferenced.
- ldy #octlProc+2 ;Get hi-word of proc address.
- lda [ctlPtr],y
- rts
-
- ***
-
- doActivate lda code
- cmp #activateEvt
- beq @a
- sec
- rts
-
- @a pha
- pha
- _GetPort
-
- pha ;Result space for _GetWControls.
- pha
- ldy #omessage+2 ;Find out which window we are
- lda [event],y ;talking about.
- tax
- dey
- dey
- lda [event],y
- phx
- pha
- phx
- pha
- _SetPort
-
- ldy #omodifiers ;See if we are activating.
- lda [event],y
- lsr a
- bcc @noMenuProc ;We are not, so don't update menus.
-
- pha ;See if we have a proc to set the state
- pha ;of the menus.
- jsl fmdGetMenuProc
- plx ;Lo-word of address.
- pla ;Hi-word of address.
- bne @haveMenuProc ;We have a menu proc -- go do it.
- txy
- beq @noMenuProc ;We don't have one.
-
- @haveMenuProc phk ;Push where we want to return to.
- pea @noMenuProc-1
- xba ;Push just the lo-byte as the hi-byte
- pha ;of ret addr.
- phb
- pla
- dex ;Push the lo-word minus 1 for rtl.
- phx
- rtl
-
- @noMenuProc _GetWControls
- pla
- sta ctlHndl
- pla
- sta ctlHndl+2
-
- @loop lda ctlHndl+1
- beq @exit
- jsr getCtlProc
-
- ldx #@nakend-@nak-2
- @naklook cmp >@nak,x
- beq @nextCtl
- dex
- dex
- bpl @naklook
-
- cmp #editLineControl>>16
- bne @inval ;Invalidate unless lineEdit.
- ;Invalidate this one selectively. If
- ;it is the window's target, then
- ;invalidate it.
-
- ldy #octlMoreFlags
- lda [ctlPtr],y
- bpl @nextCtl ;It doesn't need invalidating.
-
- @inval lda ctlPtr ;Push pointer to bounding rect of ctl.
- clc
- adc #octlRect
- tax
- lda ctlPtr+2
- adc #0
- pha
- phx
- _InvalRect
- jsr getCtlProc ;An easy way to redereference.
-
- @nextCtl ldy #2
- lda [ctlPtr]
- sta ctlHndl
- lda [ctlPtr],y
- sta ctlHndl+2
- bra @loop
-
- @exit _SetPort
- clc ;displayed in the correct state.
- rts
-
- @nak dc.w $8100,$8900,$8D00 ;These don't need invalidating ever.
- @nakend
-
- ***
-
- doUpdate lda code
- cmp #updateEvt
- beq @a
- sec
- rts ;Event isn't an update event.
-
- @noUpdate stz code ;We don't do this update, since the
- clc ;window that needs to be updated isn't
- rts ;the modal dialog.
-
- @a ldy #omessage+2 ;Find out which window we are
- lda [event],y ;talking about.
- sta tempwptr+2
- tax
- dey
- dey
- lda [event],y
- sta tempwptr
- tay
-
- lda flags
- and #fmdUpdateAll
- bne @doUpdate ;We are movable/modal, so update it,
- ;whatever it is.
-
- cpy dlgwptr
- bne @noUpdate ;We are modal, so don't update other
- cpx dlgwptr+2 ;windows.
- bne @noUpdate ;We are modal, so don't update other
- ;windows.
-
- @doUpdate phx ;Result space for _GetContentDraw.
- phy
- phx ;For _GetContentDraw
- phy
- _GetContentDraw
- plx
- pla
- bne @haveProc
- txy
- beq @exit
-
- @haveProc phk ;Push return address for updateProc.
- pea @retLoc-1
-
- xba ;Push just the lo-byte as the hi-byte
- pha ;of ret addr.
- phb
- pla
-
- dex ;Push the lo-word minus 1 for rtl.
- phx
-
- pei tempwptr+2
- pei tempwptr
- _BeginUpdate
-
- rtl ;Go to the updateProc.
-
- @retLoc pei tempwptr+2
- pei tempwptr
- _EndUpdate
-
- @exit clc
- rts
-
- ***
-
- doMouseDown lda code
- cmp #mouseDownEvt
- beq @a
- sec
- rts
-
- @a pha ;Find out what window we clicked on.
- pei zero
- tdc
- clc
- adc #whichWindow
- pha
- ldy #owhere+2
- lda [event],y
- sta xloc
- pha
- dey
- dey
- lda [event],y
- sta yloc
- pha
- _FindWindow
- pla
- bpl @aa
-
- tax ;Keep it for _SystemClick's use.
- lda flags
- and #fmdDeskAcc
- beq @toBeep
-
- pei event+2 ;Let the DA have some fun, too.
- pei event
- pei whichWindow+2
- pei whichWindow
- phx
- _SystemClick
- clc
- rts
-
- @aa cmp #wInDrag
- bne @b
-
- jsr isMyWindow ;See if "whichWindow" equals dlgwptr.
- bcc @toBeep ;Wrong window -- nice try, though.
-
- lda flags
- bpl @az ;@noBeep
-
- ldy #0 ;Drag resolution -- default.
- phy
- pei xloc ;Starting mouse location.
- pei yloc
- pea 8 ;TaskMaster uses this value, so we do.
- phy ;Default cursor boundary.
- phy
- pei dlgwptr+2
- pei dlgwptr
- _DragWindow
- ldy #omodifiers
- lda [event],y
- and #appleKey
- bne @az
- pei dlgwptr+2
- pei dlgwptr
- _SelectWindow
- @az brl @noBeep
-
- @b cmp #wInMenuBar
- bne @c ;Not in menu bar.
- lda flags
- lsr a
- lsr a
- bcc @toBeep ;_MenuSelect not allowed -- go do beep.
- lda flags
- and #fmdMenuSelect+fmdMenuKey
- beq @toBeep ;Modal dialog, no menus allowed, so go
- ;do beep.
- brl doMenuTask ;Movable/modal dialog, so go
- ;handle menu bar.
-
- @c cmp #wInFrame ;Don't beep if on dialog frame. This
- beq @d ;branch is the most efficient sizewise,
- ;since we won't hit any controls.
- cmp #wInContent
- bne @toBeep ;We didn't click in a content.
-
- @d jsr isMyWindow
- bcs @e
- @toBeep brl @beep
-
- @e pha
- pha
- _FrontWindow
- pei dlgwptr+2
- pei dlgwptr
- _SelectWindow
-
- pla
- plx
- cmp whichWindow
- bne @noBeep
- cpx whichWindow+2
- bne @noBeep
-
- @f pha
- pei zero
- tdc
- clc
- adc #ctlHndl
- pha
- pei xloc
- pei yloc
- pei dlgwptr+2
- pei dlgwptr
- _FindControl
- pla
- beq @noBeep ;Missed all of the controls.
-
- jsr fixLEflash
-
- pha
- pei xloc
- pei yloc
- lda #-1
- pha
- pha
- pei ctlHndl+2
- pei ctlHndl
- _TrackControl
- pla
- sta >ctlPart
- beq @noBeep
-
- ldy #owmTaskData2 ;Put the found control in TaskData2
- lda ctlHndl ;for application.
- sta [event],y
- iny
- iny
- lda ctlHndl+2
- sta [event],y
- jsr setValues
- clc
- rts
-
- @beep lda beepProc+2
- bmi @noBeep ;Negative, do nothing.
- ora beepProc
- beq @sysBeep ;Zero, regular SysBeep.
-
- pei event+2 ;Give the custom "beep" something
- pei event ;to play with.
- phk ;Push where we want to return to.
- pea @noBeep-1
- lda beepProc+1 ;Push updateProc addr and return to it.
- pha
- phb
- pla
- lda beepProc
- dec a
- pha
- rtl
- @sysBeep _SysBeep
- @noBeep clc
- rts
-
- fixLEflash jsr getCtlProc
- cmp #editLineControl>>16
- bne @rts
- ldy #octlMoreFlags
- lda [ctlPtr],y
- bmi @rts ;LineEdit control already target.
-
- ldy #octlData ;For lineEdit controls that are
- lda [ctlPtr],y ;inactive, make sure that there is no
- sta theHndl ;text currently selected. If there is,
- iny ;TrackControl will temporarily flash
- iny ;the selected range. So, we check to
- lda [ctlPtr],y ;see if we are a lineEdit control. If
- sta theHndl+2 ;we are, we see if we are active. If
- ldy #2 ;we aren't, we set selEnd to be the
- lda [theHndl] ;same as selStart. Simple, huh?
- sta thePtr
- lda [theHndl],y
- sta thePtr+2
-
- ldy #oleSelStart ;thePtr is deref'ed lineEdit record.
- lda [thePtr],y ;Set selEnd to be the same as selStart.
- iny
- iny
- sta [thePtr],y ;It is done. It is good. The end.
-
- @rts rts
-
- ***
-
- fmdGetCtlPart
- FMDGETCTLPART lda >ctlPart
- sta 4,s
- jml _fmdNoError
- ctlPart dc.w 0
-
- ***
-
- setValues pha ;Convert the control handle into an ID
- pha ;for application.
- pei ctlHndl+2
- pei ctlHndl
- _GetCtlID
- pla
- ply
- bcs @a ;List controls have non-super-control
- ;scrollbars. We therefore don't want
- ;to return a control-id here, since
- ;non-super-controls don't have an id to
- ;return anyway. (We get an error $1007
- ;if it isn't a super-control, so we
- ;don't want to return anything
- ;anything, since it garbage.)
- sta retval
- sty retval+2 ;Return the ctlID in retval.
-
- @a jsr getCtlProc ;See if radio button or checkbox.
- cmp #radioControl>>16
- beq @radioButtonHit
- cmp #checkControl>>16
- bne @rts
-
- @checkBoxHit pha
- pei ctlHndl+2
- pei ctlHndl
- _GetCtlValue
- pla
- beq @c ;Do a true NOT.
- lda #$FFFF
- @c inc a
- @d pha
- pei ctlHndl+2
- pei ctlHndl
- _SetCtlValue
- @rts rts
-
- @radioButtonHit lda #1
- bra @d
-
- doMenuTask clc
- doMenuTaskz php ;Keep carry status.
- pei event+2
- pei event
- lda #0
- pha
- pha
- bcs @b
- jsr ibeamTest
- bcc @a
- _InitCursor ;This only gets done if it is currently
- ;an ibeam.
- @a _MenuSelect ;Handle the pullDown.
- bra @c
- @b _MenuKey ;Handle the menu key.
-
- @c plp ;Restore carry status.
- ldy #owmTaskData
- lda [event],y
- beq @rts ;PullDown, cclear. MenuKey, cset.
- tax
- iny
- iny
- lda [event],y
- sta menunum
-
- cpx #250 ;See if we should open a DA.
- bcs @d
-
- lda flags ;See if we should handle DA's.
- and #fmdDeskAcc
- beq @y ;No, so hilite menu to normal.
- phx ;Open the can-o-worms.
- phx
- _InitCursor
- _OpenNDA
- pla
- bra @y ;Do _HiliteMenu and leave.
-
- @d cpx #256 ;Anything above close, let app do it.
- bcs @z ;Not an undo/cut/copy/paste/clear/close
- ;menu item.
-
- ldy wkind
- bpl @e
-
- cpx #255
- beq @closeNDA ;Go let the DA handle it.
-
- txa
- sec
- sbc #249
- pha
- pha
- _SystemEdit
- pla
- bra @y ;Do _HiliteMenu and leave.
-
- @e cpx #255
- beq @z ;Let app do close for non DA windows.
- cpx #250
- beq @z ;Let app do undo also.
-
- stx editTask ;Let cut/copy/paste know what to do.
- jsr doCutCopyPaste
-
- @y pei zero
- pei menunum
- _HiliteMenu
- clc
- rts
-
- @z stx retval ;Low-order word contains the ID # of
- ora #$8000 ;item selected. Hi-order word contains
- sta retval+2 ;the menu ID # with hi-bit turned on.
- clc ;The hi-bit is to allow the application
- ;to distinguish this from a control ID.
- ;This means ID's must be hi-bit off!!
- @rts rts
-
- @closeNDA pha
- pha
- _FrontWindow
- lda 1,s ;Be extra paranoid -- it helps.
- cmp keepPort ;Make sure that the desk accessory was
- bne @db ;not active port when fakeModalDialog
- lda 3,s ;was called. If it is, we will get
- cmp keepPort+2 ;into trouble closing it, because we
- bne @db ;will do a SetPort to keepPort when we
- lda dlgwptr ;leave. So, if keepPort is the port we
- sta keepPort ;are about to close, change it to the
- lda dlgwptr+2 ;dlgwptr (the app's dialog window).
- sta keepPort+2
- @db _CloseNDAByWinPtr
- bra @y
-
- isMyWindow lda whichWindow
- cmp dlgwptr
- bne @no
- lda whichWindow+2
- cmp dlgwptr+2
- beq @yes
- @no clc
- @yes rts
-
- ***
-
- doMenuKey lda code
- cmp #keyDownEvt
- beq @a
- sec
- @rts rts ;It isn't a menu key, since it isn't
- ;even a key.
-
- @a lda flags
- and #fmdMenuKey
- sec
- beq @rts ;Menu keys not allowed (carry is set).
-
- brl doMenuTaskz ;Carry still set, which is important.
-
- ***
-
- ibeamTest lda wkind
- clc
- bmi @rts ;Don't do our ibeam when a DA is up.
- pha ;This is so we know what cursor we
- pha ;currently have. Otherwise, we will be
- _GetCursorAdr ;setting the cursor a lot, and it will
- pha ;flash.
- pha
- jsl fmdGetIBeamAdr ;This clears carry (no error returned.)
- pla
- ply
- eor 1,s
- bne @no ;Carry is clear.
- tya
- eor 3,s
- bne @no ;Carry is clear.
- sec
- @no pla
- pla
- @rts rts ;Carry set means we now have ibeam.
-
- ENDP
-
-
- *******************************************************************************
- *******************************************************************************
- *******************************************************************************
-
- * From this point are additional entry points and useful access routines.
-
- ********************
-
- export fmdStdDrawProc
- fmdStdDrawProc PROC
- export FMDSTDDRAWPROC
-
- FMDSTDDRAWPROC pha ;What kind of window frame do we want?
- pha
- pha
- _GetPort
- _GetWFrame
- pla ;fAlert is bit 13. fFlex is bit 9.
- asl a
- asl a ;fAlert is now in bit 15.
- bmi @noFrame ;We already have a frame, and
- ;it looks maaahvelous!
-
- and #$0800 ;Bit 9 moved into bit 11.
- bne @noFrame
-
- pha
- _GetMasterSCB
- pla
- xba
- asl a
- lda #5
- bcs @in640
- lsr a
- @in640 pha ;Keep the width for _InsetRect.
- pha ;Push the width for _FrameRect.
- pea 2
- _SetPenSize
- plx ;The width for _InsetRect.
- lda #@workRect
- ldy #@workRect>>16
- phy ;Push parameters for _FrameRect.
- pha
- phy ;Push parameters for _InsetRect.
- pha
- phx ;Push the width for _InsetRect.
- pea 2
- phy ;Push parameters for _GetPortRect.
- pha
- _GetPortRect
- _InsetRect
- _FrameRect
- _PenNormal
-
- @noFrame pha
- pha
- _GetPort
- _DrawControls
- rtl
-
- @workRect ds.w 4
-
- ENDP
-
- ********************
-
- export fmdSetMenuProc
- fmdSetMenuProc PROC
- export FMDSETMENUPROC
- export fmdGetMenuProc, FMDGETMENUPROC
- import _fmdNoError
-
- FMDSETMENUPROC lda 4,s
- sta >menuProc
- lda 6,s
- sta >menuProc+2
- lda 1,s
- sta 5,s
- lda 2,s
- sta 6,s
- pla
- pla
- exit jml _fmdNoError
-
- fmdGetMenuProc
- FMDGETMENUPROC lda >menuProc
- sta 4,s
- lda >menuProc+2
- sta 6,s
- bra exit
-
- menuProc dc.l 0
-
- ENDP
-
- ********************
-
- export fmdEditMenu
- fmdEditMenu PROC
- export FMDEDITMENU
- import _fmdNoError
-
- DefineStack
-
- selStart long
- selEnd long
- leHndl long
- lePtr long
- ctlPtr long ;Must be 2nd from end of local space.
- ctlHndl long ;Must be at end of local space.
-
- sizeLocals EndLocals
-
- saveDPage word
- returnAddr block 3
-
- ***
-
- FMDEDITMENU phd ;Save directPage register.
-
- tsc ;Make space for locals, part 1.
- sec
- sbc #sizeLocals
- tcd
-
- pha ;Find out if it is a DA window.
- pha
- pha
- _FrontWindow
- _GetWKind
- pla
- bpl @a ;It is a regular window.
- pea 250
- _EnableMItem ;Enable undo.
- pea 255
- _EnableMItem ;Enable close.
- ldx #%1111 ;Enable cut/copy/paste/clear.
- brl @setMenus
-
- @a pha
- pha
- _FindTargetCtl
- bcc @aa ;There is a target, so go do some work.
- brl @noTool
-
- @aa ldy #2 ;Deref target ctl handle into ctlPtr.
- lda [ctlHndl],y
- pha
- lda [ctlHndl]
- pha
-
- tdc ;Make space for locals, part 2.
- tcs ;Stack ptr & directPage ptr agree now.
-
- ldy #octlProc+2 ;Get hi-word of proc address.
- lda [ctlPtr],y
-
-
- cmp #editTextControl>>16
- beq @textEdit ;It is TextEdit tool.
- cmp #editLineControl>>16
- bne @noTool ;Not LineEdit tool.
-
- @lineEdit ldy #octlData ;Get the lineEdit handle from
- lda [ctlPtr],y ;the control's data field.
- sta leHndl
- iny
- iny
- lda [ctlPtr],y
- sta leHndl+2
-
- ldy #2 ;Dereference leHndl.
- lda [leHndl]
- sta lePtr
- lda [leHndl],y
- sta lePtr+2
-
- ldx #0
- jsr canWePaste
-
- ldy #oleSelStart
- lda [lePtr],y
- iny
- iny
- cmp [lePtr],y
- beq @setMenus
- txa
- ora #%1011 ;Enable cut/copy/clear.
- tax
- bra @setMenus
-
- @textEdit ldy #0
- phy
- tdc
- clc
- adc #selStart
- pha
- phy
- adc #selEnd-selStart
- pha
- pei ctlHndl+2
- pei ctlHndl
- _TEGetSelection
- ldx #%1011
- lda selStart
- cmp selEnd
- bne @hasSelect
- lda selStart+2
- cmp selEnd+2
- bne @hasSelect
- ldx #0
-
- @hasSelect jsr canWePaste
-
- ldy #$28+2 ;Find out if we are read-only.
- lda [ctlPtr],y
- and #$0400 ;Bit 26, please.
- beq @setMenus
-
- txa ;Don't allow cut & paste.
- and #2
- tax
- bra @setMenus
-
- @noTool ldx #0 ;Bit 0 for cut, 1 for copy,
- ;2 for paste.
- @setMenus txa
- ldy #251
- jsr setOneMenu
- jsr setOneMenu
- jsr setOneMenu
- jsr setOneMenu
-
- @exit tdc ;Remove local space.
- clc
- adc #sizeLocals
- tcs
- pld ;Restore directPage register.
- jml _fmdNoError
-
- setOneMenu lsr a
- pha
- phy
- phy
- bcs @enable
- @disable _DisableMItem
- bra @a
- @enable _EnableMItem
- @a ply
- iny
- pla
- rts
-
- canWePaste txa ;Assume no paste.
- and #$FFFF-4
- pha
-
- pha ;See if paste should be available.
- pha
- pea 0
- _GetScrapSize
- plx
- ply
-
- pla ;Get cut/copy/paste status back.
-
- bcs @exit ;Error, so no paste.
- phy
- ply
- bne @yes
- txy
- beq @exit
- @yes ora #4
-
- @exit tax
- rts
-
- ENDP
-
- ********************
-
- export fmdFindCursorCtl
- fmdFindCursorCtl PROC
- export FMDFINDCURSORCTL
- import _fmdNoError
-
- DefineStack
-
- hndl long ;Must be at 1,s
- ctlHndl long
- ctlPtr long
-
- sizeLocals EndLocals
-
- saveDPage word
- returnAddr block 3
-
- BegParms
- wptr long
- yloc word
- xloc word
- ctlHndlPtr long ;Where to store the control handle.
- sizeParms EndParms
-
- ctlPart word
-
- ***
-
- FMDFINDCURSORCTL phd ;Save directPage register.
- tsc ;Make space for locals.
- sec
- sbc #sizeLocals
- tcs
- tcd ;Set directPage register.
-
- pei wptr+2
- pei wptr
- _GetWControls ;Result space already there (hndl).
-
- stz ctlPart ;Assume failure.
- stz ctlHndl
- stz ctlHndl+2
-
- @loop lda hndl+1
- beq @exit ;No more controls to check.
-
- ldy #2 ;Deref hndl.
- lda [hndl]
- sta ctlPtr
- lda [hndl],y
- sta ctlPtr+2
-
- pha ;Result space for _PtInRect
- pea 0 ;Push pointer to point.
- tdc
- clc
- adc #yloc
- pha
- lda ctlPtr ;Push ptr to bounding rect of ctl.
- clc
- adc #octlRect
- tax
- lda ctlPtr+2
- adc #0
- pha
- phx
- _PtInRect
- pla
- beq @nextCtl
-
- sta ctlPart
- lda hndl ;Copy the temp hndl to the "real" one.
- sta ctlHndl
- lda hndl+2
- sta ctlHndl+2
-
- ldy #octlProc+2 ;Get hi-word of proc address.
- lda [ctlPtr],y
- cmp #editTextControl>>16
- bne @exit
-
- @nextCtl ldy #2
- lda [ctlPtr] ;Get the next control handle.
- sta hndl
- lda [ctlPtr],y
- sta hndl+2
- bra @loop
-
- @exit lda ctlHndl ;Return the ctl hndl (could be NULL).
- sta [ctlHndlPtr]
- lda ctlHndl+2
- ldy #2
- sta [ctlHndlPtr],y
-
- tsc ;Get rid of local variables.
- clc
- adc #sizeLocals
- tcs
- pld ;Restore directPage register.
- lda 1,s ;Move return address.
- sta 1+sizeParms,s
- lda 2,s
- sta 2+sizeParms,s
- tsc ;Get rid of passed parameters.
- adc #sizeParms
- tcs
- jml _fmdNoError
-
- ENDP
-
- ********************
-
- * Here are some useful routines for control information access via a ctl ID.
-
- ********************
-
- * This routine takes a window pointer, a lineEdit control ID, and a pointer to
- * a pascal string. It stuffs the pascal string into the lineEdit control.
- * It also select the full range of the text. This is useful because the
- * target control should have all the text selected when a dialog comes up.
- * Doing it here means you don't have to do it elsewhere.
-
- export fmdLESetText
- fmdLESetText PROC
- export FMDLESETTEXT
- export fmdLEGetText, FMDLEGETTEXT
- import _fmdSetError
-
- DefineStack
-
- ctlHndl long
- ctlPtr long
- leHndl long
- lePtr long
- lineHndl long
- linePtr long
- cstr long
- lineLength word
- rect block 8 ;Must be > oleViewRect ($10)
-
- sizeLocals EndLocals
-
- saveDPage word
- returnAddr block 3
-
- BegParms
- pstr long ;Pointer to string space.
- lineEditID long ;ID of lineEdit control.
- wptr long ;Window that owns the control.
- sizeParms EndParms
-
- ***
-
- FMDLESETTEXT jsr lineEditSetup ;Set up everything we need.
- bcs exit ;Couldn't dereference for some reason.
-
- pei cstr+2 ;Set text to c-string.
- pei cstr
- lda [pstr] ;Get length of pascal string.
- and #$FF
- pha
- pei leHndl+2
- pei leHndl
- _LESetText
- bcs exit
-
- pha ;Invalidate view rect of lineEdit.
- pha
- _GetPort ;Save the current port.
- pei wptr+2
- pei wptr
- _SetPort ;Make the window the current port
- ;(for _InvalRect).
-
- jsr lineEditDeref ;Redereference -- slow but small.
- ldy #oleSelStart
- lda #0
- pha ;Hi-word for _InvalRect.
- sta [lePtr],y
- iny
- iny ;Point at leSelEnd.
- lda [pstr] ;Get length of pascal string.
- and #$FF
- sta [lePtr],y
-
- ldy #oleViewRect+6 ;Copy lineEdit viewRect into rect.
- @a lda [lePtr],y
- tyx
- sta <rect-oleViewRect,x
- dey
- dey
- cpy #oleViewRect
- bcs @a
-
- tdc ;Hi-word alreay on stack. (It's a 0).
- adc #rect ;Carry still clear.
- pha
- _InvalRect ;Inval that rect.
-
- _SetPort ;Put the port back.
-
- exitNoErr lda #0 ;Return no error.
- exit tay ;Save error code.
-
- tdc ;Get rid of local variables.
- clc
- adc #sizeLocals
- tcs
- pld ;Restore directPage register.
-
- lda 1,s ;Move return address.
- sta 1+sizeParms,s
- lda 2,s
- sta 2+sizeParms,s
-
- tsc ;Pull passed parms off stack.
- adc #sizeParms
- tcs
-
- tya ;Recover error code.
- jml _fmdSetError
-
- ***
-
- fmdLEGetText
- FMDLEGETTEXT jsr lineEditSetup ;Set up everything we need.
- bcs exit ;Couldn't dereference for some reason.
-
- pei linePtr+2 ;Copy the text into the string.
- pei linePtr
- pei cstr+2
- pei cstr
- pea 0
- pei lineLength
- _BlockMove
-
- ldy lineLength ;Store the p-string length and also
- tya ;terminate the string for the c dudes.
- shortm ;Use 8-bit accumulator.
- sta [pstr] ;Save the p-string length byte.
- lda #0
- sta [cstr],y ;Terminate the c-string.
- longm ;Set accumulator back to 16-bit.
-
- bra exitNoErr ;Return no error.
-
- ***
-
- lineEditSetup plx ;Save return address so stack frame
- ;setup works.
-
- phd ;Save directPage register.
- tsc ;Make space for locals.
- sec
- sbc #sizeLocals
- tcs
- tcd ;Set directPage register.
-
- phx ;Put return address back.
-
- lda pstr ;Also point past p-string length
- ldx pstr+2 ;for c-strings.
- inc a
- bne @a
- inx
- @a sta cstr
- stx cstr+2
-
- pha ;Get the control handle via wptr,id.
- pha
- pei wptr+2
- pei wptr
- pei lineEditID+2
- pei lineEditID
- _GetCtlHandleFromID
- plx
- stx ctlHndl
- plx
- stx ctlHndl+2
- bcs rts1
-
- ldy #2 ;Dereference ctlHndl.
- lda [ctlHndl]
- sta ctlPtr
- lda [ctlHndl],y
- sta ctlPtr+2
-
- ldy #octlData ;Get the lineEdit handle from
- lda [ctlPtr],y ;the control's data field.
- sta leHndl
- iny
- iny
- lda [ctlPtr],y
- sta leHndl+2
-
- lineEditDeref ldy #2 ;Dereference leHndl.
- lda [leHndl]
- sta lePtr
- lda [leHndl],y
- sta lePtr+2
-
- ldy #oleLength
- lda [lePtr],y
- sta lineLength
-
- ldy #oleLineHandle
- lda [lePtr],y
- sta lineHndl
- iny
- iny
- lda [lePtr],y
- sta lineHndl+2
-
- ldy #2 ;Dereference lineHndl.
- lda [lineHndl]
- sta linePtr
- lda [lineHndl],y
- sta linePtr+2
- clc ;Everything worked.
-
- rts1 rts
-
- ENDP
-
- ********************
-
- export fmdWhichRadio
- fmdWhichRadio PROC
- export FMDWHICHRADIO
- import _fmdSetError
-
- DefineStack
-
- ctlHndl long ;Must be at 1,s
- ctlPtr long
- ctlID long ;ID of some radio button control.
- theRadBut word
- notHere word ;Flag for active button not found.
-
- sizeLocals EndLocals
-
- saveDPage word
- returnAddr block 3
-
- BegParms
- famNum word
- wptr long ;Window that owns the control.
- sizeParms EndParms
-
- radioNum word
-
- ***
-
- FMDWHICHRADIO phd ;Save directPage register.
- tsc ;Make space for locals.
- sec
- sbc #sizeLocals
- tcs
- tcd ;Set directPage register.
-
- lda #$FFFF ;This is supposed to be a bogus value
- sta radioNum ;(0 is legit).
- sta notHere ;Assume we won't find active radio
- sta ctlID+2 ;button of correct family number.
-
- pei wptr+2
- pei wptr
- _GetWControls ;Result space already there (ctlHndl).
- bcs @exit
-
- @loop lda ctlHndl+1 ;See if we have a NULL handle yet.
- beq @endLoop
-
- jsr @derefCtl ;Deref ctlHndl into ctlPtr.
-
- ldy #octlProc+2 ;Get hi-word of proc address.
- lda [ctlPtr],y
- cmp #radioControl>>16
- bne @nextCtl ;Not a radio button. Skip it.
-
- ldy #octlFlag
- lda [ctlPtr],y
- and #$7F
- cmp famNum ;See if it is "our" family.
- bne @nextCtl ;Not related.
-
- ldy #octlID+2 ;See if this is the smallest ctlID for
- lda [ctlPtr],y ;our family yet.
- tax
- dey
- dey
- lda [ctlPtr],y
- cpx ctlID+2
- bcc @smaller
- bne @a ;It isn't.
- cmp ctlID
- bcs @a ;It isn't.
- @smaller sta ctlID ;It is, so remember it.
- stx ctlID+2
-
- @a tax
- ldy #octlValue
- lda [ctlPtr],y
- beq @nextCtl ;This isn't the active radio button.
- stx theRadBut ;This is the one, so remember enough
- stz notHere ;of it. Also, flag we found it.
-
- @nextCtl ldy #2
- lda [ctlPtr]
- sta ctlHndl
- lda [ctlPtr],y
- sta ctlHndl+2
- bra @loop
-
- @endLoop lda notHere ;See if we found it. If we didn't,
- bmi @b ;return $FFFF to indicate this.
- lda theRadBut
- sec
- sbc ctlID
- @b sta radioNum ;This is what the programmer was
- ;yearning for.
-
- lda #0 ;Return no error.
-
- @exit tay ;Save error code.
-
- tdc ;Get rid of local variables.
- clc
- adc #sizeLocals
- tcs
- pld ;Restore directPage register.
-
- lda 1,s ;Move return address.
- sta 1+sizeParms,s
- lda 2,s
- sta 2+sizeParms,s
-
- tsc ;Pull passed parms off stack.
- adc #sizeParms
- tcs
-
- tya ;Recover error code.
- jml _fmdSetError
-
- @derefCtl ldy #2
- lda [ctlHndl]
- sta ctlPtr
- lda [ctlHndl],y
- sta ctlPtr+2
- rts
-
- ENDP
-
- ********************
-
- export fmdIBeamCursor
- fmdIBeamCursor PROC
- export FMDIBEAMCURSOR
- export fmdInitIBeam, fmdGetIBeamAdr, fmdSetIBeam
- export FMDINITIBEAM, FMDGETIBEAMADR, FMDSETIBEAM
- import _fmdNoError
-
- FMDIBEAMCURSOR lda >curIBeam+2 ;Change the cursor to current ibeam.
- pha
- lda >curIBeam
- pha
- _SetCursor
- bra exit
-
- fmdInitIBeam
- FMDINITIBEAM lda #ibeamCursor ;Make default ibeam current ibeam.
- sta >curIBeam
- lda #ibeamCursor>>16
- sta >curIBeam+2
- bra exit
-
- fmdGetIBeamAdr
- FMDGETIBEAMADR lda >curIBeam ;Return address of current ibeam.
- sta 4,s
- lda >curIBeam+2
- sta 6,s
- bra exit
-
- fmdSetIBeam
- FMDSETIBEAM lda 4,s ;Change the ibeam to alternate ibeam.
- sta >curIBeam
- lda 6,s
- sta >curIBeam+2
- lda 1,s
- sta 5,s
- lda 2,s
- sta 6,s
- pla
- pla
- exit jml _fmdNoError
-
- curIBeam dc.l 0
- ibeamCursor dc.b 9,0,3,0
- dc.b $00,$F0,$F0,$00,$00,$00
- dc.b $00,$0F,$00,$00,$00,$00
- dc.b $00,$0F,$00,$00,$00,$00
- dc.b $00,$0F,$00,$00,$00,$00
- dc.b $00,$0F,$00,$00,$00,$00
- dc.b $00,$0F,$00,$00,$00,$00
- dc.b $00,$0F,$00,$00,$00,$00
- dc.b $00,$0F,$00,$00,$00,$00
- dc.b $00,$F0,$F0,$00,$00,$00
-
- dc.b $00,$00,$00,$00,$00,$00
- dc.b $00,$00,$00,$00,$00,$00
- dc.b $00,$00,$00,$00,$00,$00
- dc.b $00,$00,$00,$00,$00,$00
- dc.b $00,$00,$00,$00,$00,$00
- dc.b $00,$00,$00,$00,$00,$00
- dc.b $00,$00,$00,$00,$00,$00
- dc.b $00,$00,$00,$00,$00,$00
- dc.b $00,$00,$00,$00,$00,$00
- dc.b 4,0,6,0
-
- ENDP
-
- ********************
-
- export fmdStartUp
- fmdStartUp PROC
- export FMDSTARTUP
-
- FMDSTARTUP lda #0
- pha
- pha
- jsl fmdSetMenuProc
- jml fmdInitIBeam
-
- ENDP
-
- ********************
-
- export fmdShutDown
- fmdShutDown PROC
- export FMDSHUTDOWN
- import _fmdNoError
-
- FMDSHUTDOWN jml _fmdNoError
-
- ENDP
-
- ********************
-
- export _fmdNoError
- _fmdNoError PROC
- export _fmdSetError, fmdGetError
-
- lda #0
-
- _fmdSetError sta >fmdErr
- bra exit
-
- fmdGetError lda >fmdErr
- sta 4,s
- exit cmp #1
- rtl
-
- fmdErr dc.w 0
-
- ENDP
-
- ********************
-
- END